package gaml.java.serializer.collection;

import gaml.error.GamlException;
import gaml.java.ClassSerializer;
import gaml.java.ClassSerializerStore;
import gaml.java.NodeObjectBridge;
import gaml.yaml.SequenceNode;
import gaml.yaml.YamlNode;
import gaml.yaml.ahchor.YamlAnchorCodeStore;
import gaml.yaml.ahchor.YamlAnchorObjectStore;

import java.util.List;


public abstract class ListSerializer <T extends List <Object>> implements ClassSerializer <T> {
	static final String incorrectNodeError = "Node [%s] should be sequence node";
	static final String incorrectObjectError = "Object [%s] should implement list";
	
	ClassSerializerStore store = null;

	public ListSerializer (ClassSerializerStore store) { this.store = store; }

	@Override
	public YamlNode createNode (YamlNode parent) { return new SequenceNode (parent); }
	
	@Override
	public YamlNode serialize (YamlNode node, T object, YamlAnchorObjectStore anchors) throws GamlException {
		if (! (node instanceof SequenceNode)) throw new GamlException (String.format (incorrectNodeError, node.toString ()));
		
		node.setTag (object.getClass ().getName ());
		for (Object child: object)
			node.addChild (NodeObjectBridge.create (child, node, (Class <Object>) child.getClass (), store).parseObject (anchors).getNode ().setTag (child.getClass ().getName ()));
		return node;
	}

	@Override
	public T restore (YamlNode node, T object, YamlAnchorCodeStore anchors) throws GamlException {
//		if (! (object instanceof List)) throw new GamlException (String.format (incorrectObjectError, object.toString ()));
		
		for (int i=0; i<node.getSequenceChildren ().size (); i++)
			try { object.add (NodeObjectBridge.create (node.getChild (i), (node.getChild (i).getTag ().isEmpty () ? Object.class : Class.forName (node.getChild (i).getTag ())), store).parseNode (anchors).getObject()); }
			catch (ClassNotFoundException e) { throw new GamlException (e); }
		return object;
	}

	@Override
	public boolean noAnchor () { return false; }
}
